package com.rykj.energy.task.message.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.rykj.energy.common.cache.CacheEntity;
import com.rykj.energy.common.cache.LocalCache;
import com.rykj.energy.common.enums.DeviceTypes;
import com.rykj.energy.common.enums.StateType;
import com.rykj.energy.common.utils.*;
import com.rykj.energy.database.pojo.BasicCamera;
import com.rykj.energy.database.pojo.BasicNotice;
import com.rykj.energy.database.pojo.MessageResult;
import com.rykj.energy.database.pojo.Organization;
import com.rykj.energy.database.pojo.vo.MsgResultVo;
import com.rykj.energy.database.server.NoticeInfoCacheServer;
import com.rykj.energy.database.service.ICameraService;
import com.rykj.energy.database.service.IMsgResultService;
import com.rykj.energy.database.service.IOrganizationService;
import com.rykj.energy.task.message.dto.MessageHeader;
import com.rykj.energy.task.message.handle.ITaskMessageHandle;
import com.rykj.energy.task.message.mq.rocketMQ.RocketMQProductClient;
import com.rykj.energy.task.message.service.HandleResult;
import com.rykj.energy.task.message.service.IMsgService;
import lombok.extern.slf4j.Slf4j;
import net.anumbrella.seaweedfs.core.FileTemplate;
import net.anumbrella.seaweedfs.core.file.FileHandleStatus;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;

import java.io.File;
import java.io.FileInputStream;
import java.util.*;

@Service("msgService")
@Slf4j
public class MsgServiceImpl implements IMsgService {

    public static String TAKS_RESULT_SPLITOR = ":";
    @Autowired
    private Map<String, ITaskMessageHandle> handleMap;

    @Autowired
    private IMsgResultService msgResultService;
    @Autowired
    private IOrganizationService orgService;
    @Autowired
    private ICameraService cameraService;

    @Autowired
    private RedisUtil redisUtil;

    @Autowired
    @Lazy
    private FileTemplate template;

    @Autowired
    @Lazy
    private RocketMQProductClient productClient;


    @Override
    public void dealCapturMsg(MessageResult msgResult, JSONObject jsonObject, List<Map<String,Object>> alarmValues,JSONObject businessCont) {
        msgResult.setCheckState("Y");
        String type =msgResult.getMsgType();
        String msgCont="";
        String cont =";";
        List<String> checkRsult =new ArrayList<>();
        String warnType="Y";
        switch (type){
            //1.管道破损,"status":"open/close"：open 开 close 关闭 一般开才告警
            case "doorOpen":
                msgCont =jsonObject.getString("status");
                if("open".equals(msgCont)){
                    cont+="管道有破损";
                }else {
                    warnType="N";
                   // cont+="管道正常";
                   // msgResultService.deleteById(msgResult.getId());
                }
                break;
            //2.油位,"number":0.5  读数是否报警上层决定
            case "yewei":
                msgCont =jsonObject.getString("number");
                cont+="液位检测值:"+msgCont.substring(0,4);
                break;
            //3.阀门开关状态,"status":"open/close":open 开 close 关闭
            case "switchs":
                msgCont =jsonObject.getString("status");
                if("open".equals(msgCont)){
                    cont+="阀门状态:开";
                }else {
                    cont+="阀门状态:关";
                }
                break;
            //4.指针表,"number":[0.5,1.1,2]"} 数字表示各区域识别的仪表刻度
            case "pointerMeter":
                msgCont =jsonObject.getString("number");
                checkRsult= Arrays.asList((msgCont.replace("[","").replace("]","")).split(","));
                for (int i=0;i<checkRsult.size();i++  ) {
                    cont+=alarmValues.get(i).get("meterName")+"检测值:"+checkRsult.get(i).substring(0,4)+";";
                }
                break;
            //5.状态指示灯,"number":[0,1,2,3]"}  0表示红灯开 1 -- 熄灭 2 -- 绿灯亮
            case "lightColor":
                warnType="N";
                String lightKey="taskId_"+msgResult.getTaskId()+"_cameraId_"+msgResult.getCameraId()+"_objectId_";
                msgCont =jsonObject.getString("number");
                checkRsult= Arrays.asList((msgCont.replace("[","").replace("]","")).split(","));
                String checkey="";
                for (int i=0;i<checkRsult.size();i++  ) {
                    checkey= lightKey+alarmValues.get(i).get("id");
                    cont+=alarmValues.get(i).get("meterName")+getClorValue(checkRsult.get(i))+";";
                   if (null!=redisUtil.get(checkey)){
                     String checkValue=  redisUtil.get(checkey)+"";
                     //指示灯状态未变化 直接返回结束
                     if(!checkValue.equals(checkRsult.get(i))){
                         warnType="Y";
                         redisUtil.set(checkey,checkRsult.get(i));
                     }
                   }else {
                       redisUtil.set(checkey,checkRsult.get(i));
                       warnType="Y";
                   }
                }
                break;
            //6.零部件脱落,"number":[0,1,2,3]"} 数字表示各区域存在N个零部件
            case "goodsFall":
                warnType="N";
                msgCont =jsonObject.getString("number");
                checkRsult= Arrays.asList(msgCont.replace("[","").replace("]",""));
                if(CollectionUtils.isNotEmpty(alarmValues)){
                    for (int i=0;i<alarmValues.size();i++) {
                        cont+=alarmValues.get(i).get("meterName")+"检测到:"+checkRsult.get(i)+"个零部件;";
                    }
                }else {
                    cont+= "检测到:"+checkRsult.get(0)+"个零部件;";
                    if(null!=businessCont.get("partsNum")){
                        String parts =businessCont.getString("partsNum");
                        List<String> partsNum =Arrays.asList(parts.replace("[","").replace("]",""));
                        if(CollectionUtils.isNotEmpty(partsNum)){
                            if(!partsNum.get(0).equals(checkRsult.get(0))){
                                warnType="Y";
                            }
                        }
                    }
                }
                break;
            case "wdjc":
               // {"code":1,"fAverageTemperature":"0","fMaxTemperature":"54.22","fMinTemperature":"16.91","fTemperatureDiff":"0"}
                    Double fMaxTemperature = jsonObject.getDouble("fMaxTemperature");
                    Double fMinTemperature = jsonObject.getDouble("fMinTemperature");
                    Double temMinSize =businessCont.getDoubleValue("tempMinSize");
                    Double temMaxSize =businessCont.getDoubleValue("tempMaxSize");
                    if(fMaxTemperature>temMaxSize){
                        cont+= "温度超过"+temMaxSize;
                    }else if (fMinTemperature<temMinSize){
                        cont+= "温度低于"+temMinSize;
                    }else if(fMaxTemperature>temMaxSize && fMinTemperature<temMinSize){
                        cont+="温度异常:最高值超过"+temMaxSize+";最低值低于"+temMinSize;
                    } else {
                        warnType="N";
                    }
                break;
        }
        msgResult.setContent(cont.substring(1));
        BasicCamera camera = cameraService.findById(msgResult.getCameraId());
        Organization org=orgService.findByOrgId(camera.getOrgId());
        BasicNotice notice = NoticeInfoCacheServer.getNotice(type);
        String msgLevel = notice != null? notice.getNoticeLevel() : null;
        msgResult.setWarningSigns(warnType);
        msgResult.setCameraNo(camera.getCamNo());
        msgResult.setCameraName(camera.getCamAlias());
        msgResult.setOrgId(org.getId());
        msgResult.setOrgNo(org.getOrgNum());
        msgResult.setOrgName(org.getName());
        msgResult.setMsgTypeCn(notice.getBusineesName());
        msgResult.setMsgLevel(msgLevel);
        msgResult.setImageTime(new Date());
        msgResultService.updateById(msgResult);
        if("Y".equals(warnType)){
            MsgResultVo resultVo =new MsgResultVo();
            resultVo.setMsgId(msgResult.getId());
            String cameraNo = msgResult.getCameraNo();
            if(cameraNo!=null&&!cameraNo.equals("")){ //针对热成像双通道摄像头统一处理编号
                cameraNo = cameraNo.split("-")[0];
            }
            resultVo.setCameraNo(cameraNo);
            resultVo.setContent(msgResult.getContent());
            resultVo.setCameraName(msgResult.getCameraName());
            resultVo.setCreateDate(msgResult.getCreateDate());
            resultVo.setImageUrl(msgResult.getImageUrl());
            String imgUrls =  msgResult.getImageUrls();
            resultVo.setImageUrls(imgUrls!=null?imgUrls.split(";"):null);
            resultVo.setBusinessCode(msgResult.getMsgType());
            resultVo.setPresetCode(msgResult.getPresetCode());
            resultVo.setVideoUrl(msgResult.getVideoUrl());
            resultVo.setOrgId(msgResult.getOrgId());
            resultVo.setOrgNo(msgResult.getOrgNo());
            productClient.sendMessage("topic-alarm",JSONObject.toJSONString(resultVo));
        }
    }

    @Override
    public void dealTaskMsg(String msg) {
        log.info("====dealMessage实时视频任务检测结果为=====：" + msg);
        MessageHeader header = JsonUtil.stringToBean(msg,MessageHeader.class);
        BasicCamera camera = cameraService.getCameraByCluster(header.getCameraId());
        Organization org=orgService.findByOrgId(camera.getOrgId());
        BasicNotice notice = NoticeInfoCacheServer.getNotice(header.getCode());
        long createDate = header.getCreateDate().getTime();
        String key = header.getCode() + "_" + header.getCameraId();
        int expireTimes = notice != null? Integer.parseInt(notice.getNoticeFrequency()):60;
        if (isDuplication(key, createDate, expireTimes, false)) {
            return ;
        }
        String msgLevel = notice != null? notice.getNoticeLevel() : null;
        Integer flowId=0 ;
        if(StringUtils.isNotEmpty(header.getFlowId())){
            if(!header.getFlowId().contains(TAKS_RESULT_SPLITOR)) {
                flowId = Integer.parseInt(header.getFlowId());
            }else {
                String[] flowIdArr = header.getFlowId().split(TAKS_RESULT_SPLITOR);
                flowId = Integer.parseInt(flowIdArr[0]);
            }
        }
        header.setCameraId(String.valueOf(camera.getId()));

        //下载报警图片
        HandleResult rs=downloadMsgFile(header,camera.getId(),org.getId(),camera.getDevType());

        MessageResult msgResult = new MessageResult();
        msgResult.setCameraId(camera.getId());
        msgResult.setCameraNo(camera.getCamNo());
        msgResult.setCameraName(camera.getCamAlias());
        msgResult.setOrgId(org.getId());
        msgResult.setOrgNo(org.getOrgNum());
        msgResult.setOrgName(org.getName());
        msgResult.setTaskId(flowId);
        msgResult.setMsgType(header.getCode());
        msgResult.setMsgTypeCn(notice.getBusineesName());
        msgResult.setMsgLevel(msgLevel);
        msgResult.setWarningSigns("Y");
        msgResult.setSourceType("computeAI");
        msgResult.setDealState(StateType.UNDEAL.getCode());
        msgResult.setCheckState("Y");
        msgResult.setRemark(msg);
        msgResult.setCreateDate(new Date());
        msgResult.setContent(notice.getBusineesName());//header.getResult().toString());
//
        ITaskMessageHandle taskMessageHandle = handleMap.get(header.getCode());
        if(null!=taskMessageHandle){
            taskMessageHandle.handleMessage(msgResult,header);
        }

        msgResult.setContent(notice.getBusineesName());//header.getResult().toString());
//
        msgResult.setImageUrl(rs.getImageUrl().split(";")[0]);
        msgResult.setImageUrls(rs.getImageUrl());
        msgResult.setVideoUrl(rs.getVideoUrl());

        msgResultService.saveMsgResult(msgResult);
        MsgResultVo resultVo =new MsgResultVo();
        resultVo.setMsgId(msgResult.getId());
        String cameraNo = msgResult.getCameraNo();
        if(cameraNo!=null&&!cameraNo.equals("")){ //针对热成像双通道摄像头统一处理编号
            cameraNo = cameraNo.split("-")[0];
        }
        resultVo.setCameraNo(cameraNo);
        resultVo.setContent(msgResult.getContent());
        resultVo.setCameraName(msgResult.getCameraName());
        resultVo.setCreateDate(msgResult.getCreateDate());
        resultVo.setImageUrl(msgResult.getImageUrl());
        String imgUrls =  msgResult.getImageUrls();
        resultVo.setImageUrls(imgUrls!=null?imgUrls.split(";"):null);
        resultVo.setBusinessCode(msgResult.getMsgType());
        resultVo.setPresetCode(msgResult.getPresetCode());
        resultVo.setVideoUrl(msgResult.getVideoUrl());
        resultVo.setOrgId(msgResult.getOrgId());
        resultVo.setOrgNo(msgResult.getOrgNo());
        productClient.sendMessage("topic-alarm",JSONObject.toJSONString(resultVo));
    }

    public boolean isDuplication(String key, long createDate,  int expireTimes, boolean isContinue) {
        boolean isduplication = true;
        CacheEntity entity = LocalCache.getCache(key);
        if(entity == null) {
            isduplication = false;
            LocalCache.addCache(key, createDate, createDate, expireTimes);
        } else {
            long mills = (long)entity.getCacheContext();
            long newmills = createDate>mills?createDate:mills;
            if(isContinue){
                LocalCache.freshCache(key, newmills);
            }
        }
        return isduplication;
    }


    private HandleResult downloadMsgFile(MessageHeader header, Integer cameraId, Integer areaId, String devType) {
        HandleResult messageHistorys = new HandleResult();
        try {
            String localTmpPath="/data/shuyouzhan/images/tmp";
            String fileToken="v32Eo2Tw+qWI/eiKW3D8ye7l19mf1NngRLushO6CumLMHIO1aryun0/Y3N3YQCv/TqzaO/TFHw4=";

            JSONObject resultJson = JSONObject.parseObject(header.getResult().toString());
            String code = header.getCode();
            Date createDate = header.getCreateDate();
            Integer flowId=0 ;
            if(StringUtils.isNotEmpty(header.getFlowId())){
                if(!header.getFlowId().contains(TAKS_RESULT_SPLITOR)) {
                    flowId = Integer.parseInt(header.getFlowId());
                }else {
                    String[] flowIdArr = header.getFlowId().split(TAKS_RESULT_SPLITOR);
                    flowId = Integer.parseInt(flowIdArr[0]);
                }
            }

            Date updateDate = header.getUpdateDate();

            String faceScore = resultJson.getString("faceScore");
            Integer userId = resultJson.getInteger("faceKey");
            String expression =resultJson.getString("expression");
//        Date time =  resultObject.getDate("time");
            BasicNotice notice = NoticeInfoCacheServer.getNotice(code);
            String msgLevel = notice != null? notice.getNoticeLevel() : null;

            String videoUrl = resultJson.getString("videoUrl");
            String imageUrlCs = resultJson.getString("imageUrl");

            System.out.println("XXXXXXXXXXXXXXXXXXXXXXXXXXXXX:imageUrlCs="+imageUrlCs);


            Date imageTime = null;
            if(resultJson.get("time")!=null){
                imageTime= resultJson.getDate("time");
            }
            String imageUrl = ";";
            String day = DateUtils.getDateToDay(new Date());
            if(!DeviceTypes.wisdomBox.getCode().equals(devType)&&!DeviceTypes.boxCamera.getCode().equals(devType)&&
                    !DeviceTypes.wisdomAIO.getCode().equals(devType)&&!DeviceTypes.AIOCamera.getCode().equals(devType)){
                //检测图片下载
                if(StringUtils.isNotEmpty(imageUrlCs)){
                    String[] iu= imageUrlCs.split(";");
                    for (String url : iu){
                        try {
                            System.out.println("XXXXXXXXXXXXXXXXXXXXXXXXXXXXX:imageUrl="+url);
                            String[] urlArrs=url.split("/");
                            String fileName=urlArrs[urlArrs.length-1];
                            HttpFileRequest.downLoadFromUrl(url,fileName,localTmpPath,fileToken);

                            //上传到文件服务器
                            File file=new File(localTmpPath+File.separator+fileName);
                            FileHandleStatus fileHandle = template.saveFileByStream(fileName, new FileInputStream(file));

                            System.out.println("XXXXXXXXXXXXXXXXXXXXXXXXXXXXX:imageFile="+fileHandle.getFileUrl());
                            imageUrl +=fileHandle.getFileUrl()+";";
                            file.delete();
                        }catch (Exception e){
                            e.printStackTrace();
                        }

                    }

                    imageUrl = imageUrl.substring(1);
                }
                //回放视频下载
                if(StringUtils.isNotEmpty(videoUrl)){
                    try {
                        System.out.println("XXXXXXXXXXXXXXXXXXXXXXXXXXXXX:videoUrl="+videoUrl);
                        String[] urlArrs=videoUrl.split("/");
                        String fileName=urlArrs[urlArrs.length-1];
                        HttpFileRequest.downLoadFromUrl(videoUrl,fileName,localTmpPath,fileToken);

                        //上传到文件服务器
                        File file=new File(localTmpPath+File.separator+fileName);
                        FileHandleStatus fileHandle = template.saveFileByStream(fileName, new FileInputStream(file));

                        System.out.println("XXXXXXXXXXXXXXXXXXXXXXXXXXXXX:videoFile="+fileHandle.getFileUrl());
                        messageHistorys.setVideoUrl(fileHandle.getFileUrl());

                        file.delete();
                    }
                    catch (Exception e){
                        e.printStackTrace();
                    }

                }

            }else {
                if(StringUtils.isNotEmpty(imageUrlCs)){
                    String array =imageUrlCs.replaceAll("\\[","").replaceAll("]","").replaceAll("\\\"","");
                    String arayimg[]=array.split(",");
                    for (String o:arayimg) {
                        imageUrl +="wisdomImg/"+o+";";
                    }
                    imageUrl= imageUrl.substring(1);
                }
            }
            messageHistorys.setImageUrl(imageUrl);
//        String faceImg = resultJson.getString("faceImg");
//        if(StringUtils.isNotEmpty(faceImg)){
//            resultDto = fileServer.getPhotoPath(faceImg,null,"/"+ FileType.businessFile.getValue()+"/"+day+"/"+code);
//            if(resultDto.isResultStatus() && !"null".equals(resultDto.getResultValue())){
//                faceImg = resultDto.getResultValue();
//            }else {
//                log.error("下载消息附件失败,info=[" + JsonUtil.beanToString(header) + "]");
//                return null;
//            }
//        }
//        Organization org = organizationService.findById(areaId);
//        String msgTypeCn = dataDictService.findTaskNameByCode(code);

//        if(code.equals("qycr")){
//            msgTypeCn="巡检";
//        }



//        messageHistorys.setCameraId(cameraId);
//        messageHistorys.setUserId(StringUtils.isEmpty(userId)?null:userId + "");
//        messageHistorys.setFaceScore(faceScore);
////        messageHistorys.setVideoUrl(videoUrl);
////        messageHistorys.setFaceImg(faceImg);
//        messageHistorys.setMsgType(code);
////        messageHistorys.setMsgTypeCn(msgTypeCn);
//        messageHistorys.setCreateDate(createDate);
//        messageHistorys.setTaskId(flowId);
//        messageHistorys.setDealState("N");
//        messageHistorys.setDealResult("unDeal");
//        messageHistorys.setExpression(expression);
////        messageHistorys.setImageUrl(imageUrl);
//        messageHistorys.setImageTime(imageTime==null?createDate:imageTime);
//        messageHistorys.setMsgLevel(msgLevel);
//        messageHistorys.setUpdateDate(updateDate);
//        messageHistorys.setExeId(header.getTaskId());
//        messageHistorys.setAreaId(areaId);
//        messageHistorys.setAreaName(org.getName());
        }catch (Exception e){
            e.printStackTrace();
        }

        return messageHistorys;

    }

    /**
     * 0表示红灯开 1 -- 熄灭 2 -- 绿灯亮
     * @param col
     * @return
     */
    private String getClorValue(String col){
        String colorValue=":";
        switch (col){
            case "0":
                colorValue+="红灯亮";
                break;
            case "1":
                colorValue+="熄灭";
                break;
            case "2":
                colorValue+="绿灯亮";
                break;
        }
        return  colorValue;
    }
}
